template<typename T>
class TListItem : public TObject
{
protected:
	T mCurr;
        ref<TListItem<T> > mNext;
public:
	inline TListItem(T curr) : TObject(), mCurr(curr)
	{}

        inline ref<TListItem<T> >& Next()
	{
		return mNext;
	}

	inline T& GetObject()
	{
		return mCurr;
	}
};

template<class T, class Item = TListItem<T> >
class TList : public TArray<ref<Item> >
{
public:
	typedef ref<Item> ListItem;
	typedef ref<const Item> ConstListItem;
protected:
	ListItem mFirst;
	ListItem mLast;
protected:
	inline ListItem & MakeItem(T & inst)
	{
		return TArray::Add(ListItem(new ListItem::Create(inst)));
	}
	inline T & Insert(ListItem& prev, T& obj)
	{
		ListItem& newItem = MakeItem(obj);
		newItem->Next() = prev->Next();
		prev->Next() = newItem;
		return obj;
	}
public:
	typedef T		TypeReference;
	typedef Item	TypeItem;
private:
	void Dispose(void)
	{
		mFirst = NullPtr;
		mLast = NullPtr;
	}
public:
	inline TList(void) : TArray()
	{}
	virtual ~TList(void)
	{
		Dispose();
	}
public:
	inline ListItem Add(ListItem inst)
	{
		if(Length() == 0)
		{
			return mFirst = mLast = inst;
		}
		else
		{
			return mLast = mLast->Next() = inst;
		}
	}
	//
	inline T Add(T inst)
	{
		if(Length() == 0)
		{
			mFirst = mLast = MakeItem(inst);
		}
		else
		{
			mLast = mLast->Next() = MakeItem(inst);
		}
		return inst;
	}
	//
	inline virtual void Clear(void)
	{
		Dispose();
		base::Clear();	
	}

	inline virtual uint	SetLength(unsigned int dSize)
	{
		//NOTE: alloc maybe call clear for realloc array item, need save first and last item for restore after alloc:)
		//saved it
		ListItem f = mFirst, l = mLast;
		//alloc?
		uint retval = base::SetLength(dSize);
		//restore
		mFirst = f; 
		mLast = l;
		return retval;
	}
	//
	inline ListItem GetItem(uint index)
	{
		return Get(index);
	}

public://Iterator impl
	/*-------------------------------------------------------------------------
	| Iterator:
	| ------------
	| Helper for enumerable class
	---------------------------------------------------------------------------*/
	class Iterator
	{
	public:
                Iterator(ref<TList<T, Item> > src, ListItem index)
			:  mSource(src), mIndex(index)
		{}

		bool operator !=(const Iterator& it)
		{
			return(!mIndex.Equal(it.mIndex));
		}

		Iterator& operator ++(void)
		{
			mIndex = mIndex->Next();
			return *this;
		}

		ListItem& operator*(void)
		{
			return mIndex;
		}

		ListItem& operator->(void)
		{
			return mIndex;
		}
	private:
                ref<TList<T, Item> > mSource;
		ListItem mIndex;
	};

	/*-------------------------------------------------------------------------
	| ConstIterator:
	| ------------
	| Helper for enumerable class
	---------------------------------------------------------------------------*/
	class ConstIterator
	{
	public:
                ConstIterator(ref<TList<T, Item> > src, ListItem index)
			:  mSource(src), mIndex(index)
		{}

		bool operator !=(const Iterator& it)
		{
			return(!mIndex.Equal(it.mIndex));
		}

		ConstIterator& operator ++(void)
		{
			mIndex = mIndex->Next();
			return *this;
		}

		ListItem operator*(void)
		{
			return mIndex;
		}
		ListItem operator->(void)
		{
			return mIndex;
		}
	private:
                ref<TList<T, Item> > mSource;
		ListItem mIndex;
	};

	inline Iterator Begin(void)
	{
		return Iterator(this, mFirst);
	}
	inline Iterator End(void)
	{
		return Iterator(this, NullPtr);
	}
};


template<class T, class Item = TListItem<T> >
class List : public ref<TList<T, Item> >
{
public:
	typedef ref<Item> ListItem;
public:
	inline List() : ref() {}
        inline List(ref<TList<T, Item> > copy) : ref(copy) {} // for Cast
};
